package com.gt.common;

import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.databind.MapperFeature;
import com.fasterxml.jackson.databind.PropertyNamingStrategy;
import com.fasterxml.jackson.dataformat.xml.XmlMapper;
import lombok.experimental.UtilityClass;
import org.dom4j.*;

import java.util.*;

/**
 * @author wangdong
 * @since 2022-08-16
 */
@UtilityClass
public class XmlUtil2 {

    /**
     * xml转map 带属性
     * @param xmlStr
     * @param needRootKey 是否需要在返回的map里加根节点键
     * @return
     * @throws DocumentException
     */
    public static Map xmlToMapWithAttr(String xmlStr, boolean needRootKey) throws DocumentException {
        Document doc = DocumentHelper.parseText(xmlStr);
        Element root = doc.getRootElement();
        Map<String, Object> map = (Map<String, Object>) xmlToMapWithAttr(root);
        if(root.elements().size()==0 && root.attributes().size()==0){
            return map; //根节点只有一个文本内容
        }
        if(needRootKey){
            //在返回的map里加根节点键（如果需要）
            Map<String, Object> rootMap = new HashMap<String, Object>();
            rootMap.put(root.getName(), map);
            return rootMap;
        }
        return map;
    }

    /**
     * xml转map 带属性
     * @param element
     * @return
     */
    private static Object xmlToMapWithAttr(Element element) {
        // System.out.println(element.getName());
        Map<String, Object> map = new LinkedHashMap<String, Object>();
        List<Element> elements = element.elements();

        List<Attribute> listAttr = element.attributes(); // 当前节点的所有属性的list
        boolean hasAttributes = false;
        for (Attribute attr : listAttr) {
            hasAttributes = true;
            map.put("@" + attr.getName(), attr.getValue());
        }

        if (elements.size() == 0) {
            // map.put(element.getName(), element.getText());
            if (hasAttributes) {
                map.put("#text", element.getText());
            } else {
                map.put(element.getName(), element.getText());
            }

            if (!element.isRootElement()) {
                // return element.getText();
                if (!hasAttributes) {
                    return element.getText();
                }
            }
        } else if (elements.size() == 1) {
            map.put(elements.get(0).getName(),
                    xmlToMapWithAttr(elements.get(0)));
        } else if (elements.size() > 1) {
            // 多个子节点的话就得考虑list的情况了，比如多个子节点有节点名称相同的
            // 构造一个map用来去重
            Map<String, Element> tempMap = new LinkedHashMap<String, Element>();
            for (Element ele : elements) {
                tempMap.put(ele.getName(), ele);
            }
            Set<String> keySet = tempMap.keySet();
            for (String string : keySet) {
                Namespace namespace = tempMap.get(string).getNamespace();
                List<Element> elements2 = element.elements(new QName(string,
                        namespace));
                // 如果同名的数目大于1则表示要构建list
                if (elements2.size() > 1) {
                    List<Object> list = new ArrayList<Object>();
                    for (Element ele : elements2) {
                        list.add(xmlToMapWithAttr(ele));
                    }
                    map.put(string, list);
                } else {
                    // 同名的数量不大于1则直接递归去
                    map.put(string, xmlToMapWithAttr(elements2.get(0)));
                }
            }
        }

        return map;
    }

    /**
     * javaBean转xml
     *
     * @param javaBean javaBean对象
     * @return
     */
    public static String javaBean2Xml(Object javaBean) {
        try {
            XmlMapper xmlMapper = new XmlMapper();
            xmlMapper.setDefaultUseWrapper(false);
            //字段为null，自动忽略，不再序列化
            xmlMapper.setSerializationInclusion(JsonInclude.Include.NON_NULL);
            //XML标签名:使用骆驼命名的属性名，
            xmlMapper.setPropertyNamingStrategy(PropertyNamingStrategy.UPPER_CAMEL_CASE);
            //设置转换模式
            xmlMapper.enable(MapperFeature.USE_STD_BEAN_NAMING);
            return xmlMapper.writeValueAsString(javaBean);
        } catch (Exception e) {
            System.out.println("对象转xml失败=====>"+javaBean);
            return null;
        }
    }

//    public static void main(String[] args){
//
//
//        //图像类
//        List<ExaminationImage> examinationImageList=new ArrayList<>();
//        ExaminationImage examinationImage=new ExaminationImage();
//        examinationImage.setId("1");
//        examinationImage.setContent("这是第一张图片");
//        ExaminationImage examinationImage1=new ExaminationImage();
//        examinationImage.setId("2");
//        examinationImage.setContent("这是第2张图片");
//        examinationImageList.add(0,examinationImage);
//        examinationImageList.add(1,examinationImage1);
//        // ExaminationItems 节点
//        ExaminationItems examinationItems=new ExaminationItems();
//        examinationItems.setCode("01");
//        examinationItems.setName("ExaminationItems 节点");
//        examinationItems.setValue("ExaminationItems节点值");
//        //ExamRptCont 节点
//        ExamRptCont examRptCont=new ExamRptCont();
//        examRptCont.setId("1");
//        examRptCont.setCode("0001");
//        examRptCont.setExaminationItems(examinationItems);
//        examRptCont.setExaminationImageList(examinationImageList);
//        examRptCont.setFindings("aaasds");
//        examRptCont.setIs_abnormal("adsd");
//        examRptCont.setResult("sdad");
//        examRptCont.setUrl("http://baidu.cpm");
//
//        //ExamReportInfo 节点
//        ExamReportInfo examReportInfo =new ExamReportInfo();
//        examReportInfo.setExamRptCont(examRptCont);
//        examReportInfo.setApplier("sdasd");
//        examReportInfo.setApplierID("sdasdadaaa");
//        //ReportBody 节点
//        ReportBody reportBody=new ReportBody();
//        reportBody.setExamReportInfo(examReportInfo);
//        //ReportHead 节点
//        ReportHead reportHead=new ReportHead();
//        reportHead.setUserid("111");
//        reportHead.setTransNo("qqq");
//        reportHead.setSource("sss");
//        reportHead.setPassword("123");
//        //Report 节点
//        Report report=new Report(reportHead,reportBody);
//        System.out.println(javaBean2Xml(report));
//    }

}
